﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml.Linq;
using YAPL.Language.Ast;
using YAPL.Language.SourceParser.XML.NodeParsers;
using YAPL.Language.SourceParser.XML.NodeParsers;

namespace YAPL.Language.SourceParser.XML {
	public class XmlInputParser : InputParser {
		private readonly Dictionary<string, XmlExpressionParser> _nodeParsers = new Dictionary<string, XmlExpressionParser>();
		public XmlInputParser(InputInfo inputInfo) : base(inputInfo) {
			_nodeParsers.Add(XmlNames.ProgramDefExpression, new XmlProgramDefParser(this));
			_nodeParsers.Add(XmlNames.FunctionDefExpression, new XmlFunctionDefParser(this));
			_nodeParsers.Add(XmlNames.FunctionCallExpression, new XmlFunctionCallParser(this));
			_nodeParsers.Add(XmlNames.ReturnExpression, new XmlReturnParser(this));
			_nodeParsers.Add(XmlNames.CodeBlockExpression, new XmlCodeBlockParser(this));
			_nodeParsers.Add(XmlNames.ConstantExpression, new XmlConstantParser(this));
			_nodeParsers.Add(XmlNames.ParameterExpression, new XmlParameterParser(this));

			_nodeParsers.Add(XmlNames.VariableExpression, new XmlVariableParser(this));
			_nodeParsers.Add(XmlNames.InstanceVariableExression, new XmlInstanceVariableParser(this));
			_nodeParsers.Add(XmlNames.ClassReferenceExression, new XmlClassReferenceParser(this));
			_nodeParsers.Add(XmlNames.ClassDefExpression, new XmlClassDefParser(this));

			_nodeParsers.Add(XmlNames.AssignmentExpression, new XmlAssignmentParser(this));
			_nodeParsers.Add(XmlNames.BinaryExpression, new XmlBinaryParser(this));
			_nodeParsers.Add(XmlNames.UnaryExpression, new XmlUnaryParser(this));

			_nodeParsers.Add(XmlNames.ConditionalExpression, new XmlConditionalParser(this));
			_nodeParsers.Add(XmlNames.ConditionalThenExpression, new XmlCodeBlockParser(this));
			_nodeParsers.Add(XmlNames.ConditionalElseExpression, new XmlCodeBlockParser(this));

			_nodeParsers.Add(XmlNames.WhileExpression, new XmlWhileParser(this));
			_nodeParsers.Add(XmlNames.WhileBodyExpression, new XmlCodeBlockParser(this));
		}
		public override Expression ParseInput() {
			var xmlInput = XDocument.Load(_inputInfo.InputFileName);
			return ParseNode(xmlInput.Root);
		}
		public Expression ParseNode(XElement node) {
			return _nodeParsers[node.Name.LocalName].ParseNode(node);
		}
	}
}